//
//  KATCycleAnimationView.m
//  KATFramework
//
//  Created by Kantice on 2017/5/2.
//  Copyright © 2017年 KatApp. All rights reserved.
//

#import "KATCycleAnimationView.h"



@interface KATCycleAnimationView ()


///移动变化内容的动画封装
@property(nonatomic,retain) KATSprite *contentSprite;

///移动变化内容的尺寸
@property(nonatomic,assign) CGSize contentSize;

///是否为垂直方向移动(初始化后不能修改)
@property(nonatomic,assign) BOOL isMovingVertical;

///系统刷屏动作
@property(nonatomic,copy) void (^actions)(void);


@end



@implementation KATCycleAnimationView

/*
// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect {
    // Drawing code
}
*/


#pragma -mark 类方法


//获取实例
+ (instancetype)animationWithFrame:(CGRect)frame content:(UIView *)content distance:(double)distance andVertical:(BOOL)vertical
{
    return [self animationWithFrame:frame content:content interval:1 distance:distance andVertical:vertical];
}


//获取实例
+ (instancetype)animationWithFrame:(CGRect)frame content:(UIView *)content interval:(int)interval distance:(double)distance andVertical:(BOOL)vertical
{
    if(!content)
    {
        return nil;
    }
    
    KATCycleAnimationView *anim=[[[self alloc] init] autorelease];
    
    anim.clipsToBounds=YES;
    anim.frame=frame;
    anim.contentSize=content.bounds.size;
    anim.frameDistance=distance;
    anim.isMovingVertical=vertical;
    anim.frameInterval=interval;
    anim.isMovingBackward=NO;
    anim.actions=nil;

    //构造sprite
    anim.contentSprite=[KATSprite sprite];
    
    //禁用交互
    anim.contentSprite.interactInAnimating=NO;
    anim.contentSprite.userInteractionEnabled=NO;
    
    //平铺内容，设置动画
    if(anim.isMovingVertical)//垂直模式
    {
        //平铺的个数(前后填充+最少内容填充个数)
        int count=2+(int)(anim.bounds.size.height/anim.contentSize.height+0.5);
        
        //水平居中
        anim.contentSprite.frame=CGRectMake((anim.bounds.size.width-anim.contentSize.width)*0.5, -anim.contentSize.height, anim.contentSize.width, anim.contentSize.height*count);
        
        //最终要生产的平铺内容
        UIView *contents=[[[UIView alloc] init] autorelease];
        contents.bounds=anim.contentSprite.bounds;
        
        //平铺
        for(int i=0;i<count;i++)
        {
            //生成内容图片
            UIImageView *iv=[[[UIImageView alloc] initWithImage:[KATImageUtil imageFromView:content]] autorelease];
            iv.frame=CGRectMake(0, i*anim.contentSize.height, anim.contentSize.width, anim.contentSize.height);
            iv.contentMode=UIViewContentModeScaleAspectFit;
            
            [contents addSubview:iv];
        }
        
        //最终内容转换成图片
        UIImageView *img=[[[UIImageView alloc] initWithImage:[KATImageUtil imageFromView:contents]] autorelease];
        img.frame=contents.bounds;
        
        //把最终生存的图片添加到Sprite
        [anim.contentSprite addSubview:img];
    }
    else//水平模式
    {
        //平铺的个数(前后填充+最少内容填充个数)
        int count=2+(int)(anim.bounds.size.width/anim.contentSize.width+0.5);
        
        //垂直居中
        anim.contentSprite.frame=CGRectMake(-anim.contentSize.width, (anim.bounds.size.height-anim.contentSize.height)*0.5, anim.contentSize.width*count, anim.contentSize.height);
        
        //最终要生产的平铺内容
        UIView *contents=[[[UIView alloc] init] autorelease];
        contents.bounds=anim.contentSprite.bounds;
        
        //平铺
        for(int i=0;i<count;i++)
        {
            //生成内容图片
            UIImageView *iv=[[[UIImageView alloc] initWithImage:[KATImageUtil imageFromView:content]] autorelease];
            iv.frame=CGRectMake(i*anim.contentSize.width, 0, anim.contentSize.width, anim.contentSize.height);
            iv.contentMode=UIViewContentModeScaleAspectFit;
            
            [contents addSubview:iv];
        }
        
        //最终内容转换成图片
        UIImageView *img=[[[UIImageView alloc] initWithImage:[KATImageUtil imageFromView:contents]] autorelease];
        img.frame=contents.bounds;
        
        //把最终生存的图片添加到Sprite
        [anim.contentSprite addSubview:img];
    }
    
    //添加sprite
    [anim addSubview:anim.contentSprite];
    
    return anim;
}


//获取实例(直接用图片)
+ (instancetype)animationWithFrame:(CGRect)frame image:(UIImage *)image size:(CGSize)size bias:(float)bias interval:(int)interval distance:(double)distance andVertical:(BOOL)vertical
{
    if(!image)
    {
        return nil;
    }
    
    KATCycleAnimationView *anim=[[[self alloc] init] autorelease];
    
    anim.clipsToBounds=YES;
    anim.frame=frame;
    anim.contentSize=size;
    anim.frameDistance=distance;
    anim.isMovingVertical=vertical;
    anim.frameInterval=interval;
    anim.isMovingBackward=NO;
    anim.actions=nil;
    
    //构造sprite
    anim.contentSprite=[KATSprite sprite];
    
    //禁用交互
    anim.contentSprite.interactInAnimating=NO;
    anim.contentSprite.userInteractionEnabled=NO;
    
    //平铺内容，设置动画
    if(anim.isMovingVertical)//垂直模式
    {
        //平铺的个数(前后填充+最少内容填充个数)
        int count=2+(int)(anim.bounds.size.height/anim.contentSize.height+0.5);
        
        //水平居中
        anim.contentSprite.frame=CGRectMake((anim.bounds.size.width-anim.contentSize.width)*0.5, -anim.contentSize.height, anim.contentSize.width, anim.contentSize.height*count);
        
        //最终要生产的平铺内容
        UIView *contents=[[[UIView alloc] init] autorelease];
        contents.bounds=anim.contentSprite.bounds;
        
        //平铺
        for(int i=0;i<count;i++)
        {
            //生成内容图片
            UIImageView *iv=[[[UIImageView alloc] initWithImage:image] autorelease];
            iv.frame=CGRectMake(0, i*anim.contentSize.height, anim.contentSize.width, anim.contentSize.height+bias);
            iv.contentMode=UIViewContentModeScaleAspectFill;
            
            [contents addSubview:iv];
        }
        
        //把最终生存的图片添加到Sprite
        contents.frame=contents.bounds;
        [anim.contentSprite addSubview:contents];
    }
    else//水平模式
    {
        //平铺的个数(前后填充+最少内容填充个数)
        int count=2+(int)(anim.bounds.size.width/anim.contentSize.width+0.5);
        
        //垂直居中
        anim.contentSprite.frame=CGRectMake(-anim.contentSize.width, (anim.bounds.size.height-anim.contentSize.height)*0.5, anim.contentSize.width*count, anim.contentSize.height);
        
        //最终要生产的平铺内容
        UIView *contents=[[[UIView alloc] init] autorelease];
        contents.bounds=anim.contentSprite.bounds;
        
        //平铺
        for(int i=0;i<count;i++)
        {
            //生成内容图片
            UIImageView *iv=[[[UIImageView alloc] initWithImage:image] autorelease];
            iv.frame=CGRectMake(i*anim.contentSize.width, 0, anim.contentSize.width+bias, anim.contentSize.height);
            iv.contentMode=UIViewContentModeScaleAspectFill;
            
            [contents addSubview:iv];
        }
        
        //把最终生存的图片添加到Sprite
        contents.frame=contents.bounds;
        [anim.contentSprite addSubview:contents];
    }
    
    //添加sprite
    [anim addSubview:anim.contentSprite];
    
    return anim;
}



#pragma -mark 对象方法


//开始
- (void)play
{
    if(!_actions)//初始化刷屏动画
    {
        if(_isMovingVertical)//垂直方向
        {
            __block KATCycleAnimationView *anim=self;
            __block KATSprite *sp=_contentSprite;
            __block CGSize size=_contentSize;
            
            self.actions=^(void)
            {
                if(anim.isMovingBackward)//向上
                {
                    if(sp.frame.origin.y-_frameDistance<=-sp.bounds.size.height+anim.bounds.size.height)//过头
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x, -sp.bounds.size.height+anim.bounds.size.height+size.height, sp.bounds.size.width, sp.bounds.size.height);
                    }
                    else
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x, sp.frame.origin.y-_frameDistance, sp.bounds.size.width, sp.bounds.size.height);
                    }
                }
                else//向下
                {
                    if(sp.frame.origin.y+_frameDistance>=0)//过头
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x, -size.height, sp.bounds.size.width, sp.bounds.size.height);
                    }
                    else
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x, sp.frame.origin.y+_frameDistance, sp.bounds.size.width, sp.bounds.size.height);
                    }
                }
            };
        }
        else//水平方向
        {
            __block KATCycleAnimationView *anim=self;
            __block KATSprite *sp=_contentSprite;
            __block CGSize size=_contentSize;
            
            self.actions=^(void)
            {
                if(!anim.isMovingBackward)//向左
                {
                    if(sp.frame.origin.x-_frameDistance<=-sp.bounds.size.width+anim.bounds.size.width)//过头
                    {
                        sp.frame=CGRectMake(-sp.bounds.size.width+anim.bounds.size.width+size.width, sp.frame.origin.y, sp.bounds.size.width, sp.bounds.size.height);
                    }
                    else
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x-_frameDistance, sp.frame.origin.y, sp.bounds.size.width, sp.bounds.size.height);
                    }
                }
                else//向右
                {
                    if(sp.frame.origin.x+_frameDistance>=0)//过头
                    {
                        sp.frame=CGRectMake(-size.width, sp.frame.origin.y, sp.bounds.size.width, sp.bounds.size.height);
                    }
                    else
                    {
                        sp.frame=CGRectMake(sp.frame.origin.x+_frameDistance, sp.frame.origin.y, sp.bounds.size.width, sp.bounds.size.height);
                    }
                }
            };
        }
    }
    
    //开始动画
    [_contentSprite startDisplayLinkActions:_actions withFrameInterval:_frameInterval];
}


//停止
- (void)stop
{
    [_contentSprite stopDisplayLinkActions];
}


//释放内存
- (void)dealloc
{
    if(_actions)
    {
        Block_release(_actions);
        _actions=nil;
    }
    
    [_contentSprite stopDisplayLinkActions];
    
    [_contentSprite release];
    
    [super dealloc];
}



@end
